using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Authorization;
using RAG.Application.Interfaces;
using RAG.Application.Dtos;
using Microsoft.Extensions.Logging;

namespace RAG.Api.Controllers;

[ApiController]
[Route("api/[controller]")]
[Authorize]
public class VectorController : ControllerBase
{
    private readonly IVectorService _vectorService;
    private readonly ILogger<VectorController> _logger;

    public VectorController(IVectorService vectorService, ILogger<VectorController> logger)
    {
        _vectorService = vectorService;
        _logger = logger;
    }

    /// <summary>
    /// 生成文本向量
    /// </summary>
    [HttpPost("generate-embedding")]
    public async Task<IActionResult> GenerateEmbedding([FromBody] GenerateEmbeddingDto dto)
    {
        try
        {
            var embedding = await _vectorService.GenerateEmbeddingAsync(dto.Text);
            
            var result = new
            {
                Text = dto.Text,
                Embedding = embedding,
                Dimension = embedding.Length
            };

            return Ok(new { code = 200, message = "向量生成成功", data = result });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "生成向量失败");
            return StatusCode(500, new { code = 500, message = "生成向量失败", data = new { error = ex.Message } });
        }
    }

    /// <summary>
    /// 批量生成向量
    /// </summary>
    [HttpPost("generate-embeddings")]
    public async Task<IActionResult> GenerateEmbeddings([FromBody] GenerateEmbeddingsDto dto)
    {
        try
        {
            var embeddings = await _vectorService.GenerateEmbeddingsAsync(dto.Texts);
            
            var result = new
            {
                Texts = dto.Texts,
                Embeddings = embeddings,
                Count = embeddings.Count,
                Dimension = embeddings.FirstOrDefault()?.Length ?? 0
            };

            return Ok(new { code = 200, message = "批量向量生成成功", data = result });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "批量生成向量失败");
            return StatusCode(500, new { code = 500, message = "批量生成向量失败", data = new { error = ex.Message } });
        }
    }

    /// <summary>
    /// 计算向量相似度
    /// </summary>
    [HttpPost("calculate-similarity")]
    public async Task<IActionResult> CalculateSimilarity([FromBody] CalculateSimilarityDto dto)
    {
        try
        {
            var similarity = await _vectorService.CalculateSimilarityAsync(dto.Vector1, dto.Vector2);
            
            var result = new
            {
                Vector1 = dto.Vector1,
                Vector2 = dto.Vector2,
                Similarity = similarity
            };

            return Ok(new { code = 200, message = "相似度计算成功", data = result });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "计算相似度失败");
            return StatusCode(500, new { code = 500, message = "计算相似度失败", data = new { error = ex.Message } });
        }
    }

    /// <summary>
    /// 向量相似度搜索
    /// </summary>
    [HttpPost("search-similar")]
    public async Task<IActionResult> SearchSimilar([FromBody] VectorSearchDto dto)
    {
        try
        {
            var results = await _vectorService.SearchSimilarVectorsAsync(dto.QueryVector, dto.Vectors, dto.TopK);
            
            var result = new
            {
                QueryVector = dto.QueryVector,
                Results = results,
                TotalResults = results.Count
            };

            return Ok(new { code = 200, message = "向量搜索成功", data = result });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "向量搜索失败");
            return StatusCode(500, new { code = 500, message = "向量搜索失败", data = new { error = ex.Message } });
        }
    }

    /// <summary>
    /// 获取向量
    /// </summary>
    [HttpGet("{chunkId}")]
    public async Task<IActionResult> GetVector(Guid chunkId)
    {
        try
        {
            var vector = await _vectorService.GetVectorAsync(chunkId);
            
            if (vector == null)
            {
                return NotFound(new { code = 404, message = "向量不存在" });
            }

            var result = new
            {
                ChunkId = chunkId,
                Vector = vector,
                Dimension = vector.Length
            };

            return Ok(new { code = 200, message = "获取向量成功", data = result });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "获取向量失败");
            return StatusCode(500, new { code = 500, message = "获取向量失败", data = new { error = ex.Message } });
        }
    }

    /// <summary>
    /// 删除向量
    /// </summary>
    [HttpDelete("{chunkId}")]
    public async Task<IActionResult> DeleteVector(Guid chunkId)
    {
        try
        {
            var success = await _vectorService.DeleteVectorAsync(chunkId);
            
            if (!success)
            {
                return NotFound(new { code = 404, message = "向量不存在" });
            }

            return Ok(new { code = 200, message = "向量删除成功" });
        }
        catch (Exception ex)
        {
            _logger.LogError(ex, "删除向量失败");
            return StatusCode(500, new { code = 500, message = "删除向量失败", data = new { error = ex.Message } });
        }
    }
}

/// <summary>
/// 生成向量DTO
/// </summary>
public class GenerateEmbeddingDto
{
    public string Text { get; set; } = null!;
}

/// <summary>
/// 批量生成向量DTO
/// </summary>
public class GenerateEmbeddingsDto
{
    public List<string> Texts { get; set; } = new();
}

/// <summary>
/// 计算相似度DTO
/// </summary>
public class CalculateSimilarityDto
{
    public float[] Vector1 { get; set; } = null!;
    public float[] Vector2 { get; set; } = null!;
}

/// <summary>
/// 向量搜索DTO
/// </summary>
public class VectorSearchDto
{
    public float[] QueryVector { get; set; } = null!;
    public List<VectorData> Vectors { get; set; } = new();
    public int TopK { get; set; } = 5;
}
